﻿#include "lua/lauxlib.h"
#include "lua/lua.h"
#include "lua/lualib.h"
#include "lua_user/lua_lvgl_lib.h"
#include "lvgl/lvgl.h"

#define META_STR1 "ts"

typedef struct lua_ts
{
    int x;
    int y;
    int z;
} lua_ts;

static int create(lua_State *L)
{

    // lua_ts *a = lv_mem_alloc(sizeof(lua_ts));
    lua_ts *a = lua_newuserdata(L, sizeof(lua_ts));
    a->x = 1;
    a->y = 2;
    a->z = 5;

    // lua_pushlightuserdata(L, (void *)a);

    luaL_setmetatable(L, META_STR1);
    return 1;
}

static int get(lua_State *L)
{
    lua_ts *a = (lua_ts *)lua_touserdata(L, 1);

    printf("get %d:%d:%d\r\n", a->x, a->y, a->z);
    return 1;
}

static int set(lua_State *L)
{
    lua_ts *a = (lua_ts *)lua_touserdata(L, 1);
    int x = luaL_checkinteger(L, 2);
    int y = luaL_checkinteger(L, 3);
    int z = luaL_checkinteger(L, 4);
    a->x = x;
    a->y = y;
    a->z = z;
    printf("set %d:%d:%d\r\n", x, y, z);
    return 1;
}

static int print(lua_State *L)
{
    char *buff = luaL_checkstring(L, 1);

    // lua_pushlstring(L, buff, len);
    lua_pushstring(L, buff);
    return 1;
}

static int get_miso(lua_State *L)
{
    int num = 4;
    char buf[10] = {1, 2, 3, 4};
    for (int i = 0; i < num; i++)
    {
        lua_pushinteger(L, buf[i]);
    }
    return num;
}

static int lua_auto_gc(lua_State *L)
{
    lua_ts *a = (lv_obj_t *)luaL_checkudata(L, 1, META_STR1);
    luaL_argcheck(L, a != NULL, 1, "invalid user data");
    if (a)
    {
        //lv_obj_del(lv_obj);
        printf("del\r\n");
    }
    return 0;
}

static const struct luaL_Reg arraylib_f[] = {
    {"create", create},
    {"print", print},
    {"get_miso", get_miso},
    {NULL, NULL}};

static const struct luaL_Reg arraylib_m[] = {
    {"get", get},
    {"set", set},
    {"__gc", lua_auto_gc},
    {NULL, NULL}};

int _lvgl_struct_area_t_newindex(lua_State *L)
{
    lua_ts *a = (lua_ts *)lua_touserdata(L, 1);
    const char *key = luaL_checkstring(L, 2);
    if (!strcmp("x", key))
    {
        a->x = luaL_optinteger(L, 3, 0);
    }
    else if (!strcmp("y", key))
    {
        a->y = luaL_optinteger(L, 3, 0);
    }
    else if (!strcmp("z", key))
    {
        a->z = luaL_optinteger(L, 3, 0);
    }
    return 0;
}

LUALIB_API int lua_array_funinit(lua_State *L)
{
    luaL_newlib(L, arraylib_f);
    luaL_newmetatable(L, META_STR1);  /* create metatable for file handles */
    lua_pushvalue(L, -1);            /* push metatable */
    lua_setfield(L, -2, "__index");  /* metatable.__index = metatable */
    luaL_setfuncs(L, arraylib_m, 0); /* add file methods to new metatable */
    lua_pop(L, 1);                   /* pop new metatable */

    //luaL_newmetatable(L, META_STR1);
    //lua_pushcfunction(L, _lvgl_struct_area_t_newindex);
    //lua_setfield(L, -2, "__newindex"); //__newindex 只能赋值
    //lua_pop(L, 1);
    return 1;
}
